package com.example.demo.services;

import com.example.demo.entity.Kitting.*;
import com.example.demo.entity.Product.Files;
import com.example.demo.repository.FilesRepository;
import com.example.demo.repository.KittingRepository;
import com.example.demo.repository.UsersRepository;
import jakarta.persistence.EntityManager;
import jakarta.persistence.ParameterMode;
import jakarta.persistence.PersistenceContext;
import jakarta.persistence.StoredProcedureQuery;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
public class KittingService {

    @Autowired
    @PersistenceContext
    private final EntityManager entityManager;

    @Autowired
    private KittingRepository repo;
    @Autowired
    private FilesRepository filesRepo;
    @Autowired
    private UsersRepository userRepo;


    public KittingService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public KittingProductDTO getProduct(String productCode, String waCode) {
        if (isPureNumber(productCode)) {
            //ID
            productCode = repo.getBillNoByID(Long.valueOf(productCode));
        }else {
            productCode = repo.getBillNo(productCode);
        }

        System.out.println(productCode);
        if (productCode != null && !productCode.trim().isEmpty()) {
            Integer result = repo.queryEndQty(productCode, waCode);
            int endQty = result != null ? result : 0;
            if (endQty < 0) {
                endQty = 0;
            }
            KittingProduct product = repo.getProductByBillNo(productCode);
            String imageUrl = getImageUrl(product.getGoodsCode());
            KittingProductDTO dto = new KittingProductDTO(
                    productCode,
                    product.getPlanQty(),
                    product.getGoodsCode(),
                    product.getGoodsName(),
                    product.getDesignNumberVerSpec(),
                    product.getPlanQty().subtract(new BigDecimal(endQty)),
                    //product.getPlanQty(),
                    product.getProductCode(),
                    imageUrl
            );
            System.out.println(product.getPlanQty());
            System.out.println(endQty);
            System.out.println(dto.getNotInQty());
            System.out.println(dto);
            return dto;
        }
        return null;
    }


    public String getProductPDf(String productCode) {
        return filesRepo.findPDF(productCode).getFilePathname();
    }

    public boolean isPureNumber(String text) {
        if (text == null || text.isEmpty()) {
            return false;
        }
        return text.matches("\\d+");
    }

    public List<KittingWA> queryWaCode(String userID, String property) {
        return repo.queryWaCode(userID, property);
    }

    public int addStorageArea(String userID, String productBillNo, String waCode, String qtyS, String overInQtyS) {
        String storageArea = "999";
        int qty = Integer.parseInt(qtyS);
        //int overInQty = Integer.parseInt(overInQtyS);
        int overInQty = 0;
        System.out.println(overInQty);
        try {
            String username = userRepo.userName(userID);
            String planCode = repo.getPlanCodeByCode(productBillNo);
            String productCode = repo.getProductCode(productBillNo);

            LocalDateTime now = LocalDateTime.now();
            DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
            String nowDateTime = now.format(formatter);

            if (planCode != null && !planCode.trim().isEmpty()) {
                int result1 = repo.addPointList(productBillNo, waCode, qty, overInQty, username, nowDateTime);
                if (result1 == 1) {
                    repo.addStorageList(storageArea, planCode, productBillNo, productCode, username, nowDateTime);
                }
                int endQty = repo.queryEndQty(productBillNo, waCode);
                int planQty = repo.queryPlanQty(productBillNo);
                int notInQty = planQty - endQty;
                return 1;
            }else {
                return 0;
            }
        }catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }

    public KittingQty getQty(String goodsCode, String productCode, String productBillNo) {
        String planCode = repo.getPlanCodeByCode(productBillNo);
        StoredProcedureQuery query = entityManager.createStoredProcedureQuery("P_count_kitting")
                .registerStoredProcedureParameter("plan_code", String.class, ParameterMode.IN)
                .registerStoredProcedureParameter("product_code", String.class, ParameterMode.IN)
                .registerStoredProcedureParameter("goods_code", String.class, ParameterMode.IN)
                .setParameter("plan_code", planCode)
                .setParameter("product_code", productCode)
                .setParameter("goods_code", goodsCode);
        KittingQty kQty = new KittingQty();
        kQty.setQty(repo.getQty(productBillNo, goodsCode));
        kQty.setCode(planCode);
        System.out.println(kQty);
        return kQty;
    }

    public List<Object[]> callPWAGetKittingGoodsListNew(String productBillNo) {
        // 创建存储过程查询
        StoredProcedureQuery query = entityManager.createStoredProcedureQuery("P_WA_get_kitting_goods_list_new")
                .registerStoredProcedureParameter("product_bill_no", String.class, ParameterMode.IN)
                .setParameter("product_bill_no", productBillNo);

        // 执行存储过程
        query.execute();

        // 获取结果集（存储过程的 SELECT 查询结果）
        List<Object[]> resultList = query.getResultList();

        return resultList;
    }


    public List<Map<String, Object>> getKittingGoodsList(String productBillNo) {
        // 调用存储过程获取原始结果
        List<Object[]> rawResults = callPWAGetKittingGoodsListNew(productBillNo);

        // 将 Object[] 转换为 Map（更易读的结构）
        List<Map<String, Object>> resultMaps = rawResults.stream().map(row -> {
            Map<String, Object> map = new HashMap<>();
            map.put("productBillNo", row[0]);      // product_bill_no
            map.put("goodsCode", row[1]);          // goods_code
            map.put("goodsName", row[2]);          // goods_name
            map.put("planQty", row[3]);            // plan_qty
            map.put("configureQty", row[4]);       // configure_qty
            map.put("kittingPointQty", row[5]);    // kitting_point_qty
            map.put("designNumberVerSpec", row[6]); // design_number_ver_spec
            map.put("billStatus", row[7]);         // bill_status
            map.put("billType", row[8]);           // bill_type
            return map;
        }).collect(Collectors.toList());
        System.out.println("result:" + resultMaps);
        return resultMaps;
    }

    public int onQty(String productBillNo) {
        List<Map<String, Object>> list = getKittingGoodsList(productBillNo);
        int minNum = 0;
        int qty = 0;
        double aa = -19.0;
        double aa2 = -19.0;
        double c = 2.0;
        if (!list.isEmpty()) {
            //获取最小的比例，零件点数/零件计划数量，用于获取最小可配套量
            for(int i = 0; i < list.size(); i++) {
                Map<String, Object> firstRow = list.get(i);
                BigDecimal planQtyS1 = new BigDecimal(firstRow.get("planQty").toString());
                double planQtyS = planQtyS1.doubleValue();
                int planQty = (int) planQtyS;
                int kittingPointQty = Integer.parseInt(firstRow.get("kittingPointQty").toString());
                int num = planQty - kittingPointQty;
                System.out.println("planQty:" + planQty + "num:" + num + "minNum:" + minNum);
                if (num <= 0 && minNum == 0) {
                    minNum = planQty;
                    continue;
                }else if (num <= 0) {
                    if (minNum > planQty) {
                        minNum = planQty;
                    }
                    continue;
                }
                double a = (double) kittingPointQty / planQty;
                if(c > a) {
                    c = a;
                    aa = kittingPointQty;
                    aa2 = planQty;
                }
            }
            //获取产品计划数
            BigDecimal getPlanQtyS = repo.getPlanQty(productBillNo);
            double getPlanQty = getPlanQtyS.doubleValue();
            //获取一套产品需要的零件数量
            double productQtyOnly = aa2 / getPlanQty;
            //获取最终可成套数量
            qty = (int) (aa / productQtyOnly);
            System.out.println(aa + "," + aa2);
            System.out.println(getPlanQty + "," + productQtyOnly + "," + qty);
        }
        return qty;
    }
    /* 组件齐套 */
    public String getProductCodeByBillNo(String productBillNo) {
        return repo.getProductCode(productBillNo);
    }

    /* 工序进度 */
    public List<KittingWp> getWpSchedule(String billNo) {
        System.out.println(repo.getWpSchedule(billNo));
        return repo.getWpSchedule(billNo);
    }

    public String getImageUrl(String goodsCode){
        System.out.println(goodsCode);
        Files files = filesRepo.findImg(goodsCode);
        System.out.println(files);
        String imageUrl = files.getFilePathname();
        System.out.println(imageUrl);
        return imageUrl;
    }
}
